#include "Node.h"

//Base positions
static COORD WALLPOS[4] = { PosMod/2,	0,
							PosMod/2,	PosMod,
							PosMod,		PosMod/2,
							0,			PosMod/2};
static COORD FILLERPOS[4] = {	0,		PosMod,
								0,		0,
								PosMod,	0,
								PosMod,	PosMod};

Node::Node()
{
	m_clppFillers	= new Wall*[AmountWalls];
	m_clppMyWalls	= new Wall*[AmountWalls];
	for(int y = 0;y < AmountWalls;++y)
	{
		m_clppFillers[y] = new Wall[AmountWalls];
		m_clppMyWalls[y] = new Wall[AmountWalls];
	}
}

//Cleans up the walls and fillers it holds
Node::~Node()
{
	for (int i = 0; i < AmountWalls;++i)
	{
		delete [] m_clppMyWalls[i];
		delete [] m_clppFillers[i];
	}
	delete [] m_clppFillers;
	delete [] m_clppMyWalls;
}

void Node::Init(int WorldX,int WorldY)
{
	//Used to tell if I need to rotate wall
	COORD DirE = GetCoord(EAST);
	COORD DirW = GetCoord(WEST);
	//Dynamically generates the wall array
	for(int y = 0;y < AmountWalls;++y)
	{
		for(int x = 0;x < AmountWalls;++x)
		{
			m_clppMyWalls[y][x].Reset();
			m_clppMyWalls[y][x].m_bActive = true;
			
			m_clppFillers[y][x].MakeFiller();
		}
	}
	
	COORD DIR;
	for(int i = 0;i < NullDirection;++i)
	{
		DIR = GetCoord((eDirections)i);

		switch(i)
		{
		case EAST:
			m_clppMyWalls[DIR.Y][DIR.X].m_bActive = false;
		case WEST:
			m_clppMyWalls[DIR.Y][DIR.X].RotateByDegree(90,0,0);
			break;
		case SOUTH:
			m_clppMyWalls[DIR.Y][DIR.X].m_bActive = false;
			break;
		}
			

		if((WorldX > (WORLD_WIDTH - 2)) || (WorldY > (WORLD_HEIGHT - 2)))
			m_clppMyWalls[DIR.Y][DIR.X].m_bActive = true;

		static COORD XY;
		XY.X = WorldX * PosMod;
		XY.Y = WorldY * PosMod;
		m_clppMyWalls[DIR.Y][DIR.X].m_vPosition = D3DXVECTOR3((float)(XY.X + WALLPOS[i].X),(float)(XY.Y + WALLPOS[i].Y),0.0f);

		m_clppFillers[DIR.Y][DIR.X].m_vPosition = D3DXVECTOR3((float)(XY.X + FILLERPOS[i].X),(float)(XY.Y + FILLERPOS[i].Y),0.0f);

		m_clppMyWalls[DIR.Y][DIR.X].SetBoundingBox(i);
	}

	if(WorldX != WORLD_WIDTH && WorldY != WORLD_HEIGHT)
	{
		DIR = GetCoord(SOUTH);
		m_clppFillers[DIR.Y][DIR.X].m_bActive = true;
	}
	else if(WorldX == WORLD_WIDTH)
	{
		DIR = GetCoord(SOUTH);
		m_clppFillers[DIR.Y][DIR.X].m_bActive = true;
		DIR = GetCoord(EAST);
		m_clppFillers[DIR.Y][DIR.X].m_bActive = true;
	}
	else if(WorldY == WORLD_HEIGHT)
	{
		DIR = GetCoord(SOUTH);
		m_clppFillers[DIR.Y][DIR.X].m_bActive = true;
		DIR = GetCoord(NORTH);
		m_clppFillers[DIR.Y][DIR.X].m_bActive = true;
	}
	else if(WorldX == WORLD_WIDTH&& WorldY == WORLD_HEIGHT)
	{
		for(int i = 0;i < NullDirection;++i)
		{
			DIR = GetCoord((eDirections)i);

			m_clppFillers[DIR.Y][DIR.X].m_bActive = true;
		}
	}
				

	m_bVisited = m_bNorth = m_bSouth = m_bEast = m_bWest = false;
}
//Returns true if any direction is possible
bool Node::CanGoDirection()
{
	if(m_bNorth || m_bSouth || m_bEast || m_bWest)
	{
		return true;
	}
	else return false;
}
//Asks if a specific direction is possible
bool Node::CanGoDirection(eDirections Direction)
{
	switch(Direction)
	{
	case NORTH:
		return m_bNorth;
		break;
	case SOUTH:
		return m_bSouth;
		break;
	case EAST:
		return m_bEast;
		break;
	case WEST:
		return m_bWest;
		break;
	}
	return false;
}
//Sets a direction to true
void Node::SetDirection(eDirections Direction,bool D)
{
	switch(Direction)
	{
	case NORTH:
		m_bNorth = D;
		break;
	case SOUTH:
		m_bSouth = D;
		break;
	case EAST:
		m_bEast = D;
		break;
	case WEST:
		m_bWest = D;
		break;
	}
}
//Breaks down a wall in whatever direction you tell it
// and sets the current node to visited
void Node::BreakWall(eDirections Direction)
{
	SetVisitState(true);
	COORD DIR = GetCoord(Direction);
	if(CheckBrick(DIR.X,DIR.Y))
			GetBrick(DIR.X,DIR.Y)->m_bActive = false;
}